package net.lwf.util.web;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;


import net.lwf.number.util.RandomNumberGenerator;

import org.apache.log4j.Logger;
import org.apache.struts.Globals;
import org.apache.struts.taglib.html.Constants;
import org.apache.struts.util.TokenProcessor;

public class StrutsTokenProcessor extends TokenProcessor {

    private static final Logger logger = Logger.getLogger(StrutsTokenProcessor.class);

    private static final String HMACSHA1 = "HmacSHA1";
    private static final String SECURITY_PROVIDER_IBMJCE = "IBMJCE";
    
    /** The singleton instance of this class. */
    private static StrutsTokenProcessor instance = new StrutsTokenProcessor();

    /** The timestamp used most recently to generate a token value. */
    private long previous = 0;
    
    /**
     * Retrieves the singleton instance of this class.
     */
    public static TokenProcessor getInstance() {
        return instance;
    }

    /**
     * Protected constructor for KPTokenProcessor. Use KPTokenProcessor.getInstance() to obtain a reference to the processor.
     */
    protected StrutsTokenProcessor() {
        super();
    }

    /**
     * Save a new transaction token in the user's current session, creating a new session if necessary.
     * @param request The servlet request we are processing
     */
    public synchronized void saveToken(HttpServletRequest request) {
        HttpSession session = request.getSession();
        String token = this.generateToken(request);
        
        if (token != null) {
            session.setAttribute(Globals.TRANSACTION_TOKEN_KEY, token);
        }
    }

    /**
     * Generate a new transaction token, to be used for enforcing a single request for a particular transaction.
     * @param request The request we are processing
     */
    public synchronized String generateToken(HttpServletRequest request) {

        HttpSession session = request.getSession();

            long current = System.currentTimeMillis();
            if (current == previous) {
                current++;
            }
            previous = current;

            String random = String.valueOf(RandomNumberGenerator.generate(10));
            return random;


    }
    
    
 
    
    /**
     *
     */

    public synchronized boolean isTokenValid(HttpServletRequest request) {
        return this.isTokenValid(request, false);
    }
    
    /**
     *
     */

    public synchronized boolean isTokenValid(HttpServletRequest request, boolean reset) {
        // Retrieve the current session for this request
        HttpSession session = request.getSession(false);

        if (session == null) {
            return false;
        }

        // Retrieve the transaction token from this session, and
        // reset it if requested
        String saved =
            (String) session.getAttribute(Globals.TRANSACTION_TOKEN_KEY);

        if (saved == null) {
            return false;
        }

        if (reset) {
            this.resetToken(request);
        }

        // Retrieve the transaction token included in this request
        String token = request.getParameter(Constants.TOKEN_KEY);

        if (token == null) {
            return false;
        }

        return saved.equals(token.trim());
    }
    
}
